using System;
using System.Collections.Generic;
using System.Linq;
using MVCMS.Core.Exceptions;
using System.Data;
namespace MVCMS.Core.Model
{
    ///<summary>Folders that contain pages or other folders</summary>
    public class CmsFolder
    {
        ///<summary>ID for the folder</summary>
        public Guid ID { get; set; }

        ///<summary>Name of the page</summary>
        public string Name { get; set; }


        ///<summary>Collection of subfolders</summary>
        public List<CmsFolder> SubFolders { get; private set; }

        /// <summary>Collection of pages </summary>
        public List<CmsPage> Pages { get; private set; }

        /// <summary> Root page of the folder.. default page that is viewed </summary>
        public CmsPage RootPage { get; private set; }

        public CmsFolder Parent
        {
            get { return Parent;}
            set
            {
                Parent.Remove(this);
                Parent = value;
            }
        }

        /// <summary>
        /// Determines whether [contains] [the specified name].
        /// </summary>
        /// <param name="name">The page name.</param>
        /// <returns>
        /// 	<c>true</c> if [contains] [the specified name]; otherwise, <c>false</c>.
        /// </returns>
        public bool Contains(string name)
        {
            if (Pages.Exists(p => p.Name == name)) return true;
            if (SubFolders.Exists(p => p.Name == name && p.RootPage != null)) return true;
            return false;
        }


        /// <summary>
        /// Existses the specified name.
        /// </summary>
        /// <param name="name">The name.</param>
        /// <returns></returns>
        public bool Exists(string name)
        {
            if (Pages.Exists(p => p.Name == name)) return true;
            if (SubFolders.Exists(p => p.Name == name)) return true;
            return false;
        }

        public void AddPage(CmsPage page)
        {
            if (Exists(page.Name)) throw new InvalidNameException();
            Pages.Add(page);
        }

        public void AddFolder(CmsFolder folder)
        {
            if (Exists(folder.Name)) throw new InvalidNameException();
            SubFolders.Add(folder);
        }

        public CmsPage GetPage(string name)
        {
            //If the {page} value in the route is null or empty and there exists a root page, return it.
            if (name == null || name.Equals(""))
            {
                if (RootPage != null) return RootPage;
                throw new InvalidNameException();
            }

            //If there exists a page with the same name as {page}, return it
            if (Pages.Exists(p => p.Name == name))
            {
                return Pages.Single(p => p.Name == name);
            }

            //If there is a folder that has the name of {page} with a root page, return it.
            if (SubFolders.Exists(p => p.Name == name && p.RootPage != null))
            {
                return SubFolders.Single(p => p.Name == name).RootPage;
            }
            throw new InvalidNameException();
        }


        public bool Remove(CmsPage page)
        {
            if(Pages.Contains(page))
            {
                Pages.Remove(page);
            }
            if(RootPage.Equals(page))
            {
                RootPage = null;
            }
            return true;
        }

        private bool Remove(CmsFolder folder)
        {
            if (folder.IsEmpty())
            {
                SubFolders.Remove(folder);
                return true;
            }
            return false;
        }

        private bool IsEmpty()
        {
            if (RootPage != null) return false;
            if (Pages.Count > 0) return false;
            if (SubFolders.Count > 0) return false;
            return true;
        }
    }
}